package cn.fintecher.pangolin.service.repair.web;

import cn.fintecher.pangolin.common.utils.BeanUtils;
import cn.fintecher.pangolin.common.utils.ZWDateUtil;
import cn.fintecher.pangolin.entity.elastic.SpecialTransferData;
import cn.fintecher.pangolin.entity.elastic.SpecialTransferPhotoData;
import cn.fintecher.pangolin.service.repair.model.request.CreateSpecialTransferDataRequest;
import cn.fintecher.pangolin.service.repair.model.request.SpecialTransferDataSearchRequest;
import cn.fintecher.pangolin.service.repair.model.request.UpdateSpecialTransferDataRequest;
import cn.fintecher.pangolin.service.repair.respository.SpecialTransferDataRepository;
import cn.fintecher.pangolin.service.repair.respository.SpecialTransferPhotoDataRepository;
import com.google.common.collect.Lists;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.elasticsearch.index.query.BoolQueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.sort.SortBuilder;
import org.elasticsearch.search.sort.SortBuilders;
import org.elasticsearch.search.sort.SortOrder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
import org.springframework.data.elasticsearch.core.query.SearchQuery;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import java.util.*;
import java.util.stream.Collectors;

import static org.elasticsearch.index.query.QueryBuilders.matchPhraseQuery;
import static org.elasticsearch.index.query.QueryBuilders.termsQuery;

/**
 * Created by hanwannan on 2017/8/27.
 */
@RestController
@RequestMapping("/api/specialTransferData")
@Api(value = "其他资料", description = "其他资料")
public class SpecialTransferDataController {
    private final Logger log = LoggerFactory.getLogger(SpecialTransferDataController.class);

    @Autowired
    private SpecialTransferDataRepository specialTransferDataRepository;

    @Autowired
    private SpecialTransferPhotoDataRepository specialTransferPhotoDataRepository;

    @GetMapping("/search")
    @ApiOperation(value = "查询其他资料", notes = "查询其他资料")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "page", dataType = "int", paramType = "query",
                    value = "页数 (0..N)"),
            @ApiImplicitParam(name = "size", dataType = "int", paramType = "query",
                    value = "每页大小."),
            @ApiImplicitParam(name = "sort", allowMultiple = true, dataType = "string", paramType = "query",
                    value = "依据什么排序: 属性名(,asc|desc). ")
    })
    public ResponseEntity<Page<SpecialTransferData>> search(Pageable pageable, SpecialTransferDataSearchRequest request) {

        SortBuilder sortBuilder = SortBuilders.fieldSort("importDate").unmappedType("date").order(SortOrder.DESC);
        SearchQuery searchQuery = new NativeSearchQueryBuilder()
                .withPageable(pageable)
                .withSort(sortBuilder)
                .withQuery(request.generateQueryBuilder()).build();
        log.info("search special transfer data : {} query :{}", request.toString(), searchQuery.getQuery().toString());
        Page<SpecialTransferData> searchPageResults = specialTransferDataRepository.search(searchQuery);
        return new ResponseEntity<>(searchPageResults, HttpStatus.OK);
    }

    @GetMapping("/searchDetails")
    @ApiOperation(value = "获取特调计生附件图片", notes = "根据用户id号获取图片明细信息")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "parentId", dataType = "String", paramType = "query", required = true,
                    value = "证件号")
    })
    public ResponseEntity<List<SpecialTransferPhotoData>> searchDetails(String parentId) {
        Iterable<SpecialTransferPhotoData> specialTransferPhotoDataIterable = searchSpecialTransferPhotoDataByidNo(parentId);
        return new ResponseEntity<>(Lists.newArrayList(specialTransferPhotoDataIterable.iterator()), HttpStatus.OK);
    }

    @GetMapping("/get")
    @ApiOperation(value = "获取其他资料", notes = "获取其他资料")
    public ResponseEntity get(String id) throws Exception {
        Optional<SpecialTransferData> byId = specialTransferDataRepository.findById(id);
        SpecialTransferData specialTransferData = byId.get();
        return ResponseEntity.ok().body(specialTransferData);
    }

    @PostMapping("/insert")
    @ApiOperation(value = "创建其他资料", notes = "创建其他资料")
    public ResponseEntity insert(@RequestBody CreateSpecialTransferDataRequest specialTransferDataRequest) throws Exception {
        log.info("Create special transfer data {}", specialTransferDataRequest);
        SpecialTransferData specialTransferData = new SpecialTransferData();
        BeanUtils.copyProperties(specialTransferDataRequest, specialTransferData);
        specialTransferData.setImportDate(ZWDateUtil.getNowDateTime());
        specialTransferData.setOperatorTime(ZWDateUtil.getNowDateTime());
        SpecialTransferData specialTransfer = specialTransferDataRepository.save(specialTransferData);
        if (specialTransferDataRequest.getCredentialSet() != null) {
            specialTransferDataRequest.getCredentialSet().forEach(specialTransferPhotoData -> {
                specialTransferPhotoData.setType(specialTransfer.getType());
                specialTransferPhotoData.setParentId(specialTransfer.getId());
            });
            specialTransferPhotoDataRepository.saveAll(specialTransferDataRequest.getCredentialSet());
        }
        return ResponseEntity.ok().body(specialTransferData);
    }

    @PostMapping("/update")
    @ApiOperation(value = "修改其他资料", notes = "修改其他资料")
    public ResponseEntity update(@RequestBody UpdateSpecialTransferDataRequest specialTransferDataRequest) throws Exception {
        Optional<SpecialTransferData> byId = specialTransferDataRepository.findById(specialTransferDataRequest.getId());
        SpecialTransferData specialTransferData = byId.get();
        BeanUtils.copyProperties(specialTransferDataRequest, specialTransferData);
        specialTransferData.setOperatorTime(ZWDateUtil.getNowDateTime());
        SpecialTransferData specialTransfer = specialTransferDataRepository.save(specialTransferData);
        if (specialTransferDataRequest.getCredentialSet() != null) {
            Iterable<SpecialTransferPhotoData> specialTransferPhotoDataIterable = specialTransferPhotoDataRepository
                    .findByParentId(specialTransferData.getId());
            specialTransferPhotoDataRepository.deleteAll(specialTransferPhotoDataIterable);

            //给附件设置类型
            specialTransferDataRequest.getCredentialSet().forEach(specialTransferPhotoData -> {
                specialTransferPhotoData.setType(specialTransferData.getType());
                specialTransferPhotoData.setParentId(specialTransfer.getId());
            });
            specialTransferPhotoDataRepository.saveAll(specialTransferDataRequest.getCredentialSet());
        }
        return ResponseEntity.ok().body(specialTransferData);
    }

//    @PostMapping("/addCredential")
//    @ApiOperation(value = "添加证件", notes = "添加证件")
//    public ResponseEntity addCredential(@RequestBody AddCredentialRequest addCredentialRequest) throws exception {
//        log.info("Add credential {}", addCredentialRequest);
//        Optional<SpecialTransferData> byId = specialTransferDataRepository.findById(addCredentialRequest.getId());
//        SpecialTransferData specialTransferData = byId.get();
//        specialTransferData.setCredentialSet(addCredentialRequest.getCredentialSet());
//        specialTransferData.setOperatorTime(ZWDateUtil.getNowDateTime());
//        specialTransferDataRepository.save(specialTransferData);
//        return ResponseEntity.ok().body(specialTransferData);
//    }

    @DeleteMapping("/delete")
    @ApiOperation(value = "删除特调资料", notes = "删除特调资料")
    public ResponseEntity delete(@RequestParam String id) {
        Optional<SpecialTransferData> specialTransferData = specialTransferDataRepository.findById(id);
        if (specialTransferData != null) {
            Iterable<SpecialTransferPhotoData> specialTransferPhotoDataIterable = specialTransferPhotoDataRepository
                    .findByParentId(id);
            specialTransferPhotoDataRepository.deleteAll(specialTransferPhotoDataIterable);
        }
        specialTransferDataRepository.deleteById(id);
        return ResponseEntity.ok().body(null);
    }

    @GetMapping("/deleteBatch")
    @ApiOperation(value = "批量删除特调资料", notes = "批量删除特调资料")
    public ResponseEntity delete(@RequestParam("id") String[] ids) {
        ArrayList<SpecialTransferData> specialTransferDataList = new ArrayList<>();
        SpecialTransferData specialTransferData = null;
        for (String id : ids) {
            specialTransferData = new SpecialTransferData();
            specialTransferData.setId(id);
            specialTransferDataList.add(specialTransferData);
        }
        specialTransferDataRepository.deleteAll(specialTransferDataList);
        return ResponseEntity.ok().body(null);
    }

    @GetMapping("/deleteByBatch")
    @ApiOperation(value = "按导入批次删除户籍资料", notes = "删除户籍资料")
    public ResponseEntity deleteByBatch(String batchNumber) {
        specialTransferDataRepository.deleteByBatchNumber(batchNumber);
        specialTransferPhotoDataRepository.deleteByBatchNumber(batchNumber);
        return ResponseEntity.ok().body(null);
    }

    /**
     * 根据id查询特调计生图片信息
     *
     * @return
     */
    public Iterable<SpecialTransferPhotoData> searchSpecialTransferPhotoDataByidNo(String id) {
        BoolQueryBuilder queryBuilder = QueryBuilders.boolQuery();
        queryBuilder.must(matchPhraseQuery("parentId.keyword", id));
        Iterable<SpecialTransferPhotoData> returnResult;
        //在系统中手动添加或附件导入的数据，是存在parentId的关联
        returnResult = specialTransferPhotoDataRepository.search(queryBuilder);
        //通过parentId查到数据，则证明是通过新系统添加的，否则则为数据迁移的数据
        if(!returnResult.iterator().hasNext()){
            Optional<SpecialTransferData> byId = specialTransferDataRepository.findById(id);
            //对于数据迁移的数据，需要通过docName和身份证号码关联
            if(byId.isPresent()){
                BoolQueryBuilder boolQuery = QueryBuilders.boolQuery();
                if(Objects.nonNull(byId.get().getImportCode()) && Objects.nonNull(byId.get().getIdNo())){
                    returnResult = specialTransferPhotoDataRepository.search(boolQuery.must(matchPhraseQuery("docName.keyword", byId.get().getImportCode()))
                            .must(matchPhraseQuery("idNo.keyword", byId.get().getIdNo())));
                }

            }
        }
        return returnResult;
    }

    public Iterable<SpecialTransferPhotoData> searchSpecialTransferPhotoDataByDate(SpecialTransferData transferData) {
        BoolQueryBuilder queryBuilder = QueryBuilders.boolQuery();
        List<SpecialTransferPhotoData> photes = transferData.getCredentialSet();
        Set<String> fileNames = photes.stream().map(SpecialTransferPhotoData::getFileName).collect(Collectors.toSet());
        queryBuilder.must(termsQuery("fileName.keyword", fileNames));
        return specialTransferPhotoDataRepository.search(queryBuilder);
    }

}
